package mx.ipn.persistencia.mysql;

import java.sql.Connection;
import java.sql.Date;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;

import mx.ipn.persistencia.FabricaDeDAOs;
import mx.ipn.persistencia.dao.BitacoraChoferUnidadDAO;
import mx.ipn.persistencia.dao.ChoferDAO;
import mx.ipn.persistencia.dao.UnidadDAO;
import mx.ipn.to.BitacoraChoferUnidadTO;
import mx.ipn.to.ChoferTO;
import mx.ipn.to.UnidadTO;
import mx.ipn.to.FechaHoraTO;


public class BitacoraChoferUnidadDAOMySQL implements BitacoraChoferUnidadDAO {
	static{FabricaDeDAOsMySQL.iniciaLog(BitacoraChoferUnidadDAOMySQL.class);}

	private static final String INSERT = "INSERT INTO bitacora_chofer_unidad (fecha,id_chofer,id_unidad) VALUES(?,?,?)";
	private static final String UPDATE = "UPDATE bitacora_chofer_unidad SET fecha=?,id_chofer=?,id_unidad=? WHERE id_operacion=?";

	private static final String FINDBYID = "SELECT * FROM bitacora_chofer_unidad WHERE id_operacion=?";

	private static final String SELECT = "SELECT * FROM bitacora_chofer_unidad";
	private static final String SELECTBYRANGOFECHA = "SELECT * FROM bitacora_chofer_unidad WHERE fecha>=? AND fecha<=?";

	private static final String SELECTBYCHOFERRANGOFECHA = "SELECT * FROM bitacora_chofer_unidad WHERE id_chofer=? AND fecha>=? AND fecha<=?";
	private static final String SELECTBYUNIDADRANGOFECHA = "SELECT * FROM bitacora_chofer_unidad WHERE id_unidad=? AND fecha>=? AND fecha<=?";

	@Override
	public BitacoraChoferUnidadTO findBitacoraChoferUnidadById(int idOperacion) {
		try {
			Connection conexion = FabricaDeDAOsMySQL.crearConexion();

			PreparedStatement ps = conexion.prepareStatement(FINDBYID);

			ps.setInt(1, idOperacion);

			ResultSet rs = ps.executeQuery();
			FabricaDeDAOs fabricaMySQL = FabricaDeDAOs
					.getFabricaDeDAOs(mx.ipn.Constantes.FABRICA_DAOS_MYSQL);
			ChoferDAO choferDAO = fabricaMySQL.getChoferDAO();
			UnidadDAO unidadDAO = fabricaMySQL.getUnidadDAO();

			if (rs.next()) {
				idOperacion = rs.getInt("id_operacion");
				java.sql.Date fecha = rs.getDate("fecha");

				ArrayList<ChoferTO> listChoferTO = new ArrayList<ChoferTO>();
				ArrayList<UnidadTO> listUnidadTO = new ArrayList<UnidadTO>();
				UnidadTO unidadTO = unidadDAO.findUnidadById(rs
						.getInt("id_unidad"));
				ChoferTO choferTO = choferDAO.findChoferById(rs
						.getInt("id_chofer"));
				listUnidadTO.add(unidadTO);
				listChoferTO.add(choferTO);

				ChoferTO[] arrChoferTO = (ChoferTO[])listChoferTO.toArray(new ChoferTO[listChoferTO.size()]);
				UnidadTO[] arrUnidadTO = (UnidadTO[])listUnidadTO.toArray(new UnidadTO[listUnidadTO.size()]);				
				
				BitacoraChoferUnidadTO bitacoraChoferUnidadTO = new BitacoraChoferUnidadTO(
						idOperacion, fecha, arrChoferTO, arrUnidadTO);
				ps.close();
				conexion.close();
				return bitacoraChoferUnidadTO;
			}
			ps.close();
			conexion.close();
			return null;

		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	@Override
	public int insertBitacoraChoferUnidad(
			BitacoraChoferUnidadTO bitacoraChoferUnidadTO) {
		try {
			Connection conexion = FabricaDeDAOsMySQL.crearConexion();

			PreparedStatement ps = conexion.prepareStatement(INSERT);

			ps.setDate(1, FechaHoraTO.getFecha(bitacoraChoferUnidadTO.getFecha()));
			ps.setInt(2, bitacoraChoferUnidadTO.getIdChofer());
			ps.setInt(3, bitacoraChoferUnidadTO.getIdUnidad());

			ps.executeUpdate();

			// atrapa el indice del campo agregado
		    int autoIncIndice = -1;
		    ResultSet rs = ps.getGeneratedKeys();

		    if (rs.next()) {
		        autoIncIndice = rs.getInt(1);
		    } else {
		    	System.err.print("No se pudo agregar campo");
		    	return 0;
		    }
			
			ps.close();
			conexion.close();

			return autoIncIndice;
		} catch (Exception e) {
			e.printStackTrace();
			return -1;
		}
	}

	@Override
	public ArrayList<BitacoraChoferUnidadTO> selectBitacoraChoferUnidad() {
		try {
			Connection conexion = FabricaDeDAOsMySQL.crearConexion();

			PreparedStatement ps = conexion.prepareStatement(SELECT);

			ResultSet rs = ps.executeQuery();
			FabricaDeDAOs fabricaMySQL = FabricaDeDAOs
					.getFabricaDeDAOs(mx.ipn.Constantes.FABRICA_DAOS_MYSQL);
			ChoferDAO choferDAO = fabricaMySQL.getChoferDAO();
			UnidadDAO unidadDAO = fabricaMySQL.getUnidadDAO();

			ArrayList<BitacoraChoferUnidadTO> coleccion = null;

			while (rs.next()) {
				if (coleccion == null)
					coleccion = new ArrayList<BitacoraChoferUnidadTO>();

				int idOperacion = rs.getInt("id_operacion");
				java.sql.Date fecha = rs.getDate("fecha");

				ArrayList<ChoferTO> listChoferTO = new ArrayList<ChoferTO>();
				ArrayList<UnidadTO> listUnidadTO = new ArrayList<UnidadTO>();
				ChoferTO choferTO = choferDAO.findChoferById(rs
						.getInt("id_chofer"));
				UnidadTO unidadTO = unidadDAO.findUnidadById(rs
						.getInt("id_unidad"));
				listChoferTO.add(choferTO);
				listUnidadTO.add(unidadTO);

				ChoferTO[] arrChoferTO = (ChoferTO[])listChoferTO.toArray(new ChoferTO[listChoferTO.size()]);
				UnidadTO[] arrUnidadTO = (UnidadTO[])listUnidadTO.toArray(new UnidadTO[listUnidadTO.size()]);				
				
				BitacoraChoferUnidadTO bitacoraChoferUnidadTO = new BitacoraChoferUnidadTO(
						idOperacion, fecha, arrChoferTO, arrUnidadTO);

				coleccion.add(bitacoraChoferUnidadTO);
			}
			ps.close();
			conexion.close();

			return coleccion;

		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	@Override
	public BitacoraChoferUnidadTO selectByChoferRangoFecha(int idChofer,
			Date inicioFecha, Date finFecha) {
		try {
			Connection conexion = FabricaDeDAOsMySQL.crearConexion();
			// Crea la fabrica especifica de MySQL
			FabricaDeDAOs fabricaMySQL = null;
			// Crea un DAO para la tabla persona
			ChoferDAO choferDAO = null;
			UnidadDAO unidadDAO = null;

			ArrayList<Integer> listIdOperacion = null;
			ArrayList<java.sql.Date> listFecha = null;
			ArrayList<ChoferTO> listChoferTO = null;
			ArrayList<UnidadTO> listUnidadTO = null;

			BitacoraChoferUnidadTO bitacoraChoferUnidadTO = null;

			PreparedStatement ps = conexion
					.prepareStatement(SELECTBYCHOFERRANGOFECHA);

			ps.setInt(1, idChofer);
			ps.setDate(2, inicioFecha);
			ps.setDate(3, finFecha);

			ResultSet rs = ps.executeQuery();

			while (rs.next()) {
				if (listIdOperacion == null) {

					listIdOperacion = new ArrayList<Integer>();
					listFecha = new ArrayList<java.sql.Date>();
					listChoferTO = new ArrayList<ChoferTO>();
					listUnidadTO = new ArrayList<UnidadTO>();

					fabricaMySQL = FabricaDeDAOs
							.getFabricaDeDAOs(mx.ipn.Constantes.FABRICA_DAOS_MYSQL);

					choferDAO = fabricaMySQL.getChoferDAO();
					unidadDAO = fabricaMySQL.getUnidadDAO();
				}
				listIdOperacion.add(rs.getInt("id_operacion"));
				listFecha.add(rs.getDate("fecha"));
				listUnidadTO.add(unidadDAO.findUnidadById(rs
						.getInt("id_unidad")));
			}
			if (listIdOperacion != null) {
				listChoferTO.add(choferDAO.findChoferById(idChofer));
				
				ChoferTO[] arrChoferTO = (ChoferTO[])listChoferTO.toArray(new ChoferTO[listChoferTO.size()]);
				UnidadTO[] arrUnidadTO = (UnidadTO[])listUnidadTO.toArray(new UnidadTO[listUnidadTO.size()]);				
				Integer[] arrIdOperacion = (Integer[])listIdOperacion.toArray(new Integer[listIdOperacion.size()]);
				Date[] arrFecha = (Date[])listFecha.toArray(new Date[listFecha.size()]);

				bitacoraChoferUnidadTO = new BitacoraChoferUnidadTO(
						arrIdOperacion, arrFecha, arrChoferTO, arrUnidadTO);
			}
			ps.close();
			conexion.close();
			return bitacoraChoferUnidadTO;

		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	@Override
	public ArrayList<BitacoraChoferUnidadTO> selectByRangoFecha(Date inicio,
			Date fin) {
		try {
			Connection conexion = FabricaDeDAOsMySQL.crearConexion();

			PreparedStatement ps = conexion
					.prepareStatement(SELECTBYRANGOFECHA);

			ps.setDate(1, inicio);
			ps.setDate(2, fin);

			ResultSet rs = ps.executeQuery();
			FabricaDeDAOs fabricaMySQL = FabricaDeDAOs
					.getFabricaDeDAOs(mx.ipn.Constantes.FABRICA_DAOS_MYSQL);
			ChoferDAO choferDAO = fabricaMySQL.getChoferDAO();
			UnidadDAO unidadDAO = fabricaMySQL.getUnidadDAO();

			ArrayList<BitacoraChoferUnidadTO> coleccion = null;

			while (rs.next()) {
				if (coleccion == null)
					coleccion = new ArrayList<BitacoraChoferUnidadTO>();

				int idOperacion = rs.getInt("id_operacion");
				java.sql.Date fecha = rs.getDate("fecha");

				ArrayList<ChoferTO> listChoferTO = new ArrayList<ChoferTO>();
				ArrayList<UnidadTO> listUnidadTO = new ArrayList<UnidadTO>();
				ChoferTO choferTO = choferDAO.findChoferById(rs
						.getInt("id_chofer"));
				UnidadTO unidadTO = unidadDAO.findUnidadById(rs
						.getInt("id_unidad"));
				listChoferTO.add(choferTO);
				listUnidadTO.add(unidadTO);

				ChoferTO[] arrChoferTO = (ChoferTO[])listChoferTO.toArray(new ChoferTO[listChoferTO.size()]);
				UnidadTO[] arrUnidadTO = (UnidadTO[])listUnidadTO.toArray(new UnidadTO[listUnidadTO.size()]);				
				
				BitacoraChoferUnidadTO bitacoraChoferUnidadTO = new BitacoraChoferUnidadTO(
						idOperacion, fecha, arrChoferTO, arrUnidadTO);

				coleccion.add(bitacoraChoferUnidadTO);
			}
			ps.close();
			conexion.close();

			return coleccion;

		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	@Override
	public BitacoraChoferUnidadTO selectByUnidadRangoFecha(int idUnidad,
			Date inicioFecha, Date finFecha) {
		try {
			Connection conexion = FabricaDeDAOsMySQL.crearConexion();
			// Crea la fabrica especifica de MySQL
			FabricaDeDAOs fabricaMySQL = null;
			// Crea un DAO para la tabla persona
			ChoferDAO choferDAO = null;
			UnidadDAO unidadDAO = null;

			ArrayList<Integer> listIdOperacion = null;
			ArrayList<java.sql.Date> listFecha = null;
			ArrayList<ChoferTO> listChoferTO = null;
			ArrayList<UnidadTO> listUnidadTO = null;

			BitacoraChoferUnidadTO bitacoraChoferUnidadTO = null;

			PreparedStatement ps = conexion
					.prepareStatement(SELECTBYUNIDADRANGOFECHA);

			ps.setInt(1, idUnidad);
			ps.setDate(2, inicioFecha);
			ps.setDate(3, finFecha);

			ResultSet rs = ps.executeQuery();

			while (rs.next()) {
				if (listIdOperacion == null) {

					listIdOperacion = new ArrayList<Integer>();
					listFecha = new ArrayList<java.sql.Date>();
					listChoferTO = new ArrayList<ChoferTO>();
					listUnidadTO = new ArrayList<UnidadTO>();

					fabricaMySQL = FabricaDeDAOs
							.getFabricaDeDAOs(mx.ipn.Constantes.FABRICA_DAOS_MYSQL);

					choferDAO = fabricaMySQL.getChoferDAO();
					unidadDAO = fabricaMySQL.getUnidadDAO();
				}
				listIdOperacion.add(rs.getInt("id_operacion"));
				listFecha.add(rs.getDate("fecha"));
				listChoferTO.add(choferDAO.findChoferById(rs
						.getInt("id_chofer")));
			}
			if (listIdOperacion != null) {
				listUnidadTO.add(unidadDAO.findUnidadById(idUnidad));

				ChoferTO[] arrChoferTO = (ChoferTO[])listChoferTO.toArray(new ChoferTO[listChoferTO.size()]);
				UnidadTO[] arrUnidadTO = (UnidadTO[])listUnidadTO.toArray(new UnidadTO[listUnidadTO.size()]);				
				Integer[] arrIdOperacion = (Integer[])listIdOperacion.toArray(new Integer[listIdOperacion.size()]);
				Date[] arrFecha = (Date[])listFecha.toArray(new Date[listFecha.size()]);

				bitacoraChoferUnidadTO = new BitacoraChoferUnidadTO(
						arrIdOperacion, arrFecha, arrChoferTO, arrUnidadTO);
			}
			ps.close();
			conexion.close();
			return bitacoraChoferUnidadTO;

		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	@Override
	public short updateBitacoraChoferUnidad(
			BitacoraChoferUnidadTO bitacoraChoferUnidadTO) {
		try {
			Connection conexion = FabricaDeDAOsMySQL.crearConexion();

			PreparedStatement ps = conexion.prepareStatement(UPDATE);

			ps.setDate(1, FechaHoraTO.getFecha(bitacoraChoferUnidadTO.getFecha()));
			ps.setInt(2, bitacoraChoferUnidadTO.getIdChofer());
			ps.setInt(3, bitacoraChoferUnidadTO.getIdUnidad());
			ps.setInt(4, bitacoraChoferUnidadTO.getIdOperacion());

			ps.executeUpdate();

			if (ps.getUpdateCount() == 0) {
				ps.close();
				conexion.close();
				return 0;
			} else {
				ps.close();
				conexion.close();
				return 1;
			}
		} catch (Exception e) {
			e.printStackTrace();
			return (short) -1;
		}
	}

}
